#include "video_service.h"

// 记录当前播放信息
_state state;

// 调用命令播放视频
int video_view(char *video_path) {
    int retval;
    if (fd_pipe[0] != 0) {
        close(fd_pipe[0]);
    }
    if (fd_pipe[1] != 0) {
        close(fd_pipe[1]);
    }
    memset(fd_pipe, 0, sizeof(fd_pipe));
    create_pipe();  // 创建无名管道
    state.pid = fork();  // 创建子进程
    if (state.pid > 1) {
    }
    if (state.pid == 0) {
        close(fd_pipe[0]);
        dup2(fd_pipe[1], 1);  //将子进程的标准输出重定向到管道的写端

        /*
        -slave 运行在从模式，从命令行读取以新行（\n）分隔开的命令行。
        -quiet 使得控制台输出消息较少。
        -idle 播放至文件结尾后，mplayer不退出。
        -input file=./myfifo 通过命令管道 ./myfifo获取命令。
        video_path 视频的绝对路径+文件名。
        NULL exec 系统调用必备。
        */
        retval = execlp("mplayer", "mplayer", "-slave", "-quiet", "-idle", "-input", "file=./myfifo", video_path, NULL);  // 调用mplayer命令
        if (retval == -1) {
            perror("execlp");
            return -1;
        }
        exit(-1);
    }
    if (state.pid < 0) {
        perror("fork error");
        exit(1);
    }
    state.is_pause = 0;
    return 0;
}

// 暂停/播放视频
int video_pause() {
    int fd = open("./myfifo", O_RDWR);
    if (-1 == fd) {
        perror("open_ifo error");
        exit(1);
    }
    write(fd, "pause\n", 6);
    close(fd);
    // send_cmd("pause\n");
    state.is_pause = (state.is_pause + 1) % 2;
    return 0;
}

// 播放上一个视频
int video_prev(arr_list *list) {
    // 当前位置在开头
    if (state.position == 0) {
        return 0;
    }
    printf("now pid = %u\n", state.pid);
    if (state.pid != 0) {
        kill(state.pid, 9);
    }

    state.position = state.position - 1;

    char video_path[128];
    strcpy(video_path, ((video *)(list->data[state.position]))->absolute_path);
    printf("video_path = %s\n", video_path);
    video_view(video_path);  // 播放视频
    strcpy(state.video_name, ((video *)(list->data[state.position]))->name);
    return 0;
}

// 播放下一个视频
int video_next(arr_list *list) {
    // 当前位置在末尾
    if (state.position == list->size - 1) {
        return 0;
    }
    printf("now pid = %u\n", state.pid);
    if (state.pid != 0) {
        kill(state.pid, 9);
    }

    state.position = state.position + 1;

    char video_path[128];
    strcpy(video_path, ((video *)(list->data[state.position]))->absolute_path);
    printf("video_path = %s\n", video_path);
    video_view(video_path);  // 播放视频
    strcpy(state.video_name, ((video *)(list->data[state.position]))->name);
    return 0;
}

// 左快进10s
int video_speed_left() {
    int fd = open("./myfifo", O_RDWR);
    if (-1 == fd) {
        perror("open_ifo error");
        exit(1);
    }
    write(fd, "seek -10\n", strlen("seek -10\n"));
    close(fd);
    return 0;
}

// 右快进10s
int video_speed_right() {
    int fd = open("./myfifo", O_RDWR);
    if (-1 == fd) {
        perror("open_ifo error");
        exit(1);
    }
    write(fd, "seek +10\n", strlen("seek +10\n"));
    close(fd);
    return 0;
}

// 生成视频预览图片
int generate_video_preview(arr_list *list) {
    int retval;
    state.pid = fork();  // 创建子进程
    if (state.pid > 1) {
    }
    if (state.pid == 0) {
        for (int i = 0; i < list->size; i++) {
            char video_path[128];
            char preview_path[128];
            memset(video_path, 0, sizeof(video_path));
            memset(preview_path, 0, sizeof(preview_path));

            // 视频路径
            strcpy(video_path, ((video *)(list->data[i]))->absolute_path);
            printf("get_video_preview video_path = %s\n", video_path);
            // 预览图路径
            strcpy(preview_path, strtok(video_path, ".")); // 截取.之前的部分
            strcat(preview_path, ".bmp"); // 拼接预览图绝对路径
            printf("get_video_preview preview_path = %s\n", preview_path);

            // 调用mplayer命令截取一帧图片生成预览图
            /* -i input.flv 截取的视频的名字
            -ss 00：00：02 这是视频的第2秒
            -frames:v 1 这代表单独这1帧
            out.png 要保存的截取的封面文件
            */
            // sprintf(jpeg_buf,"mplayer -zoom -x 150 -y 150 -ss 85 -noframedrop -nosound -vo jpeg:outdir=./%s  -frames 1 %s ",p->d_name,new_buf->pathname);
            retval = execlp("ffmpeg", "ffmpeg", "-i", ((video *)(list->data[i]))->absolute_path,
                            "-ss", "00:00:05", "-frames:v", "1", preview_path, NULL);
            if (retval == -1) {
                perror("execlp");
                break;
            }

            // ffmpeg将预览图压缩成指定的尺寸（80*80）
            retval = execlp("ffmpeg", "ffmpeg", "-i", preview_path, "-vf", "scale=80:80", preview_path, NULL);
            if (retval == -1) {
                perror("execlp");
                break;
            }

            strcpy(((video *)(list->data[i]))->preview_path, preview_path);  // 保存预览图到顺序表
        }

        exit(-1);
    }
    if (state.pid < 0) {
        perror("fork error");
        exit(1);
    }
    return 0;
}

// 选择视频播放
int video_option(arr_list *list, int position) {
    // 杀死当前进视频程
    printf("now pid = %u\n", state.pid);
    if (state.pid != 0) {
        kill(state.pid, 9);
    }

    // 计算点击的视频在顺序表中的位置
    state.position = (state.page - 1) * PAGE_NUM + position - 1;
    printf("video_option.state.position = %d\n", state.position);

    video_view(((video *)(list->data[state.position]))->absolute_path);  // 播放视频
    return 0;
}

// 视频列表向上翻页
int video_page_upward() {
    // 当前页面为第一页不做操作
    if (state.page <= 1) {
        return 0;
    }
    state.page = state.page - 1;
    show_right_list(state.page);  // 显示预览图
    return 0;
}

// 视频列表向下翻页
int video_page_down() {
    // 当前页面为最后一页不做操作
    if (state.page >= state.count_page) {
        return 0;
    }
    state.page = state.page + 1;
    show_right_list(state.page);  // 显示预览图
    return 0;
}